package it.uniroma2.exp;

import it.uniroma2.dtk.op.convolution.ReverseCircularConvolution;
import it.uniroma2.dtk.op.convolution.ShiftedCircularConvolution;
import it.uniroma2.dtk.op.convolution.ShuffledCircularConvolution;
import it.uniroma2.dtk.op.product.ReverseGammaProduct;
import it.uniroma2.dtk.op.product.ShiftedGammaProduct;
import it.uniroma2.dtk.op.product.ShuffledGammaProduct;
import it.uniroma2.exp.dtk.FunctionTester;
import it.uniroma2.exp.dtk.KernelComparison;
import it.uniroma2.exp.dtk.VectorTester;

import java.io.File;
import java.io.PrintStream;
import java.util.HashMap;

public class Experimenter {

	/**
	 * @param args
	 */
	public static void main(String[] args) {
		if (args.length == 0) {
			System.out.println("Run as it.uniroma2.exp.Experimenter n [m]...\n" +
					"where n,m,... are the numbers of the experiments to run:\n" +
					"1 - Test the properties of the different vector composition functions, for several vector sizes\n" +
					"2 - Test the dot product between two sums of k random vectors, with h vectors is common, for several vector sizes\n" +
					"3 - Test the correlation of DTK and TK values for the classic Tree Kernel, for different corpora and vector sizes\n" +
					"4 - Test the correlation of DTK and TK values for the SubPath Tree Kernel, for different corpora and vector sizes\n" +
					"5 - Test the correlation of DTK and TK values for the Route Tree Kernel, for different corpora and vector sizes");
		}
		else {
			HashMap<Integer, AbstractExperiment> expMap = new HashMap<Integer, AbstractExperiment>();
			for (String arg : args) {
				try {
					int exp = Integer.parseInt(arg);
					if (expMap.get(exp) != null)
						continue;
					if (exp == 1) {
						FunctionTester ft = new FunctionTester();
						ft.setOutputStream(new PrintStream(new File("1_function_tester.dat")));
						ft.setVectorSizeArray(new int[] {1024, 2048, 4096, 8192});
						ft.setCompositionTypeArray(new Class<?>[] {ShuffledGammaProduct.class, ShuffledCircularConvolution.class,
								ShiftedGammaProduct.class, ShiftedCircularConvolution.class, 
								ReverseGammaProduct.class, ReverseCircularConvolution.class
						});
						expMap.put(exp, ft);
					}
					else if (exp == 2) {
						VectorTester vt = new VectorTester();
						vt.setOutputStream(new PrintStream(new File("2_vector_tester.dat")));
						vt.setVectorSizeArray(new int[] {1024, 2048, 4096, 8192});
						expMap.put(exp, vt);
					}
					else if (exp == 3) {
						KernelComparison kc = new KernelComparison();
						kc.setOutputStream(new PrintStream(new File("3_kernel_comparison_TK.dat")));
						kc.setVectorSizeArray(new int[] {1024, 2048, 4096, 8192});
						kc.setRandomTreeNodes(30);
						kc.setLambdaArray(new double[]{0.2, 0.4, 0.6, 0.8, 1});
						kc.setCustomParameters(new int[][] {{0,1,2},{0},{0}});
						expMap.put(exp, kc);
					}
					else if (exp == 4) {
						KernelComparison kc = new KernelComparison();
						kc.setOutputStream(new PrintStream(new File("4_kernel_comparison_STK.dat")));
						kc.setVectorSizeArray(new int[] {1024, 2048, 4096, 8192});
						kc.setRandomTreeNodes(30);
						kc.setLambdaArray(new double[]{0.2, 0.4, 0.6, 0.8, 1});
						kc.setCustomParameters(new int[][] {{0,1,2},{0},{1}});
						expMap.put(exp, kc);
					}
					else if (exp == 5) {
						KernelComparison kc = new KernelComparison();
						kc.setOutputStream(new PrintStream(new File("5_kernel_comparison_RTK.dat")));
						kc.setVectorSizeArray(new int[] {1024, 2048, 4096, 8192});
						kc.setRandomTreeNodes(30);
						kc.setLambdaArray(new double[]{0.2, 0.4, 0.6, 0.8, 1});
						kc.setCustomParameters(new int[][] {{0,1,2},{0},{1}});
						expMap.put(exp, kc);
					}
					else
						throw new Exception("Unknown experiment: "+exp);
				}
				catch (Exception e) {
					System.err.println(e.getMessage());
				}
			}
			for (Integer i : expMap.keySet()) {
				System.out.println("Running experiment "+i+" ...");
				expMap.get(i).runAll();
			}
		}
	}

}
